package com.by.service.impl;

import com.baomidou.mybatisplus.core.conditions.update.UpdateWrapper;
import com.by.api.dto.LockStock;
import com.by.bean.UserInfo;
import com.by.context.UserContext;
import com.by.entity.*;
import com.by.mapper.*;
import com.by.msg.Constant;
import com.by.service.ProductService;
import com.by.utils.Assert;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

import java.util.List;

/**
 * @author 江俊俊
 * @version 1.0
 * @description
 * @date 2025/4/16 14:59
 * @since JDK1.8
 */
@Service
public class ProductServiceImpl implements ProductService {

    @Autowired
    SpuMapper spuMapper;

    @Autowired
    SpuDetailMapper spuDetailMapper;

    @Autowired
    SkuMapper skuMapper;

    @Autowired
    SkuStockMapper skuStockMapper;

    @Autowired
    SpuExtensionMapper spuExtensionMapper;

    @Autowired
    AttrMapper attrMapper;

    @Autowired
    AttrValueMapper attrValueMapper;

    @Autowired
    SpuAttrValueMapper spuAttrValueMapper;

    @Autowired
    SpuSkuAttrValueMapper spuSkuAttrValueMapper;

    @Autowired
    SkuStockLockMapper skuStockLockMapper;


    @Transactional
    @Override
    public int saveProduct(Spu spu) {
        // 设置用户上下文信息
        UserInfo info = UserContext.get();
        UserContext.clear();

        //保存spu
        spu.setShopId((long) info.getShopId());
        spu.setShopCategoryId((long) info.getShopCategoryId());
        int rs = spuMapper.insert(spu);
        Assert.isZero(rs, Constant.SAVE_SKU_FAIL);

        //保存spu明细
        SpuDetail spuDetail = new SpuDetail()
                .setDetail(spu.getDetail())
                .setSpuId(spu.getSpuId());
        rs = spuDetailMapper.insert(spuDetail);
        Assert.isZero(rs, Constant.SAVE_SPU_DETAIL_FAIL);


        int total = 0;
        //保存sku
        if (spu.getSkus() != null && spu.getSkus().size() > 0) {

            for (Sku sku : spu.getSkus()) {
                sku.setSpuId(spu.getSpuId());
                //保存sku
                int tmp = skuMapper.insert(sku);
                Assert.isZero(tmp, Constant.SAVE_SKU_FAIL);
                //保存sku库存
                SkuStock skuStock = new SkuStock()
                        .setSkuId(sku.getSkuId())
                        .setStock(sku.getStock())
                        .setActualStock(sku.getStock());
                tmp = skuStockMapper.insert(skuStock);
                Assert.isZero(tmp, Constant.SAVE_SKU_STOCK_FAIL);

                total += sku.getStock();
            }
        }
        //保存spu库存
        SpuExtension spuExtension = new SpuExtension().setStock(total).setSpuId(spu.getSpuId());
        rs = spuExtensionMapper.insert(spuExtension);
        Assert.isZero(rs, Constant.SAVE_SPU_EXTENSION_FAIL);


        //保存规格 获取规格 id
        String attr = "";
        for (Attr spuAttr : spu.getAttrs()) {
            int i = attrMapper.insert(spuAttr);
            Assert.isZero(i, Constant.SAVE_ATTR_FAIL);
            attr += spuAttr.getAttrId() + ",";
        }

        if (attr.length() > 0) {
            //删除最后一个逗号
            attr = attr.substring(0, attr.length() - 1);
            //保存到sku表
            for (Sku sku : spu.getSkus()) {
                sku.setAttrs(attr);
                UpdateWrapper<Sku> updateWrapper = new UpdateWrapper<>();
                updateWrapper.eq("sku_id", sku.getSkuId());
                int i = skuMapper.update(sku, updateWrapper);
                Assert.isZero(i, Constant.SAVE_SKU_FAIL);
            }
        }

        //遍历保存归格值
        for (Attr spuAttr : spu.getAttrs()) {
            for (AttrValue attrValue : spuAttr.getAttrValues()) {
                attrValue.setAttrId(spuAttr.getAttrId());
                int i = attrValueMapper.insert(attrValue);
                Assert.isZero(i, Constant.SAVE_ATTR_VALUE_FAIL);
            }
        }

        //保存spu attr value
        for (Attr spuAttr : spu.getAttrs()) {
            for (AttrValue attrValue : spuAttr.getAttrValues()) {
                SpuAttrValue spuAttrValue = new SpuAttrValue()
                        .setSpuId(spu.getSpuId())
                        .setAttrId(spuAttr.getAttrId())
                        .setAttrName(spuAttr.getName())
                        .setAttrValueId(attrValue.getAttrValueId())
                        .setAttrValueName(attrValue.getValue())
                        .setAttrDesc(spuAttr.getDesc());

                int tmp = spuAttrValueMapper.insert(spuAttrValue);
                Assert.isZero(tmp, Constant.SAVE_SPU_ATTR_VALUE_FAIL);
            }
        }

        //保存spu sku attr value

        for (Attr spuAttr : spu.getAttrs()) {
            for (AttrValue attrValue : spuAttr.getAttrValues()) {
                for (Sku sku : spu.getSkus()) {
                    SpuSkuAttrValue spuSkuAttrValue = new SpuSkuAttrValue()
                            .setSpuId(spu.getSpuId())
                            .setSkuId(sku.getSkuId())
                            .setAttrId(spuAttr.getAttrId())
                            .setAttrName(spuAttr.getName())
                            .setAttrValueId(attrValue.getAttrValueId())
                            .setAttrValueName(attrValue.getValue());

                    int tmp = spuSkuAttrValueMapper.insert(spuSkuAttrValue);
                    Assert.isZero(tmp, Constant.SAVE_SPU_SKU_ATTR_VALUE_FAIL);
                }
            }
        }

        return 1;
    }

    @Override
    @Transactional
    public int lockStock(List<LockStock> lockStocks) {
        //保存sku库存
        int i = skuStockLockMapper.batchSave(lockStocks);
        Assert.isZero(i, Constant.SAVE_SKU_STOCK_LOCK_FAIL + lockStocks);

        //更新sku库存
        lockStocks.forEach(lockStock -> {
            //更新锁定库存，可售卖库存
            int tmp = skuStockMapper.lockStock(lockStock.getSkuId(), lockStock.getNum());
            Assert.isZero(tmp, Constant.UPDATE_SKU_STOCK_FAIL + lockStock);

            //锁定spu库存
            tmp = spuExtensionMapper.lockSpuStock(lockStock.getSpuId(), lockStock.getNum());
            Assert.isZero(tmp, Constant.UPDATE_SPU_STOCK_FAIL + lockStock);

        });

        return 1;









    }


}
